#!/usr/bin/env python
# -*-coding:utf-8 -*-

from timer import Timer

__all__ = ['Task', 'setPath', 'getSrc', 'setSrc', 'getDst', 'getState', 'getPriority', 
           'setPriority', 'assignTo', 'getAssignedRobotId', 'setScheduled', 'setCompleted',
           'TaskQueue', 'append', 'remove', 'sorted', 'size']


class Task(object):
    """
    任务。机器人要完成的单个任务。单个任务定义为从地图上一个节点移动到另外一个节点。
    """
    
    STATE_NOT_SCHEDULED = 0
    STATE_PENDING       = 1
    STATE_PROCESSING    = 2
    STATE_COMPLETED     = 3
    
    #__slots__= ['_create_time', '_due_time', '_src', '_dst', '_op', '_initial_priority', \
    #            '_priority', '_release_time', '_state', '_robot', '_path']
    
    def __init__(self, due_time, src, dst, op=None, priority=0):
        """
        创建一个任务。
        :param due_time: 任务的截止时间。
        :param src: 该任务为从src节点开始移动。若src=None，则任务为机器人从其自身所在的位置移动到dst。
        :param dst: 该任务为移动到dst节点为止。
        :param op: 该任务在终点dst上要执行的操作（比如加载货物等）。
        :param priority: 该任务的优先级，默认值为0，最低优先级。
        """
        self._due_time = due_time
        self._src = src
        self._dst = dst
        self._op = op
        self._initial_priority = priority
        self._priority = priority
        self._arrival_time = float('inf')
        self._release_time = float('inf')
        self._state = Task.STATE_NOT_SCHEDULED
        self._robot = None  # which robot does this task assigned to?
        self._path = None   # which path does this task required the robot to follow
 
    def getDueTime(self):
        return self._due_time
        
    def getArrivalTime(self):
        return self._arrival_time
        
    def setArrivalTime(self, t):
        self._arrival_time = t
        
    def getReleaseTime(self):
        return self._release_time
        
    def setReleaseTime(self, t):
        self._release_time = t
        
    def isNotScheduled(self):
        return self._state == Task.STATE_NOT_SCHEDULED
               
    def isPending(self):
        return self._state == Task.STATE_PENDING
        
    def isProcessing(self):
        return self._state == Task.STATE_PROCESSING
        
    def isCompleted(self):
        return self._state == Task.STATE_COMPLETED
        
    def __lt__(self, other):
        """
        本任务是否小于任务other。优先级高的任务大。
        :param other: 将self与other这两个任务比较大小。
        """
        p1 = self.getPriority()
        p2 = other.getPriority()
        if p1 == p2:
            t1 = self.getArrivalTime()
            t2 = other.getArrivalTime()
            return t1 > t2
        else:
            return p1 < p2

    def __gt__(self, other):
        """
        本任务是否大于任务other。优先级高的任务大。
        :param other: 将self与other这两个任务比较大小。
        """
        p1 = self.getPriority()
        p2 = other.getPriority()
        if p1 == p2:
            t1 = self.getArrivalTime()
            t2 = other.getArrivalTime()
            return t1 < t2
        else:
            return p1 > p2

    def __le__(self, other):
        """
        本任务是否小于等于任务other。优先级高的任务大。
        :param other: 将self与other这两个任务比较大小。
        """
        p1 = self.getPriority()
        p2 = other.getPriority()
        if p1 == p2:
            t1 = self.getArrivalTime()
            t2 = other.getArrivalTime()
            return t1 >= t2
        else:
            return p1 <= p2

    def __ge__(self, other):
        """
        本任务是否大于等于任务other。优先级高的任务大。
        :param other: 将self与other这两个任务比较大小。
        """
        p1 = self.getPriority()
        p2 = other.getPriority()
        if p1 == p2:
            t1 = self.getArrivalTime()
            t2 = other.getArrivalTime()
            return t1 <= t2
        else:
            return p1 >= p2

    def __eq__(self, other):
        """
        本任务是否等于任务other。
        :param other: 将self与other这两个任务比较。
        """
        p1 = self.getPriority()
        p2 = other.getPriority()
        t1 = self.getArrivalTime()
        t2 = other.getArrivalTime()
        return p1 == p2 and t1 == t2

    def __ne__(self, other):
        """
        本任务是否不等于任务other。
        :param other: 将self与other这两个任务比较。
        """
        p1 = self.getPriority()
        p2 = other.getPriority()
        t1 = self.getArrivalTime()
        t2 = other.getArrivalTime()
        return not (p1 == p2 and t1 == t2)

    def setPath(self, path):
        """
        设置该任务关联的路径，由调度器调用。机器人在执行该任务时即按照该路径移动。
        :param path: 该任务为从src节点开始移动。若src=None，则任务为机器人从其自身所在的位置移动到dst。
        """
        self._path = path

    def getSrc(self):
        """
        获取该任务的起始节点。
        :return: 该任务的起始节点。
        """
        return self._src

    def setSrc(self, src):
        """
        设置该任务的起始节点。
        :param src: 设置的起始节点。
        """
        self._src = src

    def getDst(self):
        """
        获取该任务的终止节点。
        :return: 该任务的终止节点。
        """
        return self._dst
        
    def setDst(self, dst):
        """
        设置该任务的终止节点。
        :param src: 设置的终止节点。
        """
        self._dst = dst
        
    def setOperation(self, op):
        """
        设置该任务在终止节点上要执行的操作。
        :param op: 要执行的操作。
        """
        self._op = op
        
    def getOperation(self):
        """
        获取该任务在终止节点上要执行的操作。
        :return: 要执行的操作。
        """
        return self._op

    def getState(self):
        """
        获取该任务的状态。
        :return: 该任务的状态。有四种可能的状态：STATE_NOT_ASSIGNED，任务尚未分配到机器人，
                 STATE_NOT_SCHEDULED，任务已分发但尚未调度，STATE_PROCESSING正在执行，
                 STATE_COMPLETED已完成。
        """
        return self._state

    def getPriority(self):
        """
        获取该任务的优先级。
        :return: 优先级，0是最低优先级，数字越大优先级越高。
        """
        return self._priority
        
    def getInitialPriority(self):
        """
        获取该任务的优先级。
        :return: 优先级，0是最低优先级，数字越大优先级越高。
        """
        return self._initial_priority

    def setPriority(self, priority):
        """
        设置该任务的优先级。
        :param priority: 设置的优先级。0是最低优先级，数字越大优先级越高。
        """
        self._priority = priority
    
    def setPending(self):
        self._state = Task.STATE_PENDING
        
    def setUnscheduled(self):
        self._state = Task.STATE_NOT_SCHEDULED

    def setProcessing(self):
        """
        将该任务的状态设置为已调度（正在执行）。
        """
        self._state = Task.STATE_PROCESSING

    def setCompleted(self):
        """
        将该任务的状态设置为已完成。
        """
        self._state = Task.STATE_COMPLETED
 

if __name__ == '__main__':
    t0 = Task(None, 1, priority=3)
    t1 = Task(None, 2, priority=0)
    print(t0 > t1)
    
    
